package com.platform.qujia.service.impl;

import com.alibaba.fastjson.JSON;
import com.platform.qujia.controller.QuJiaPayV2Controller;
import com.platform.qujia.pojo.AppUserInfo;
import com.platform.qujia.pojo.CustomerDialogueAdTemplate;
import com.platform.qujia.pojo.Enterprise;
import com.platform.qujia.pojo.WxAddBonus;
import com.platform.qujia.service.EnterpriseService;
import com.platform.qujia.service.WeChatService;
import com.platform.qujia.utils.CodeMsg;
import com.platform.qujia.utils.HttpClientUtil;
import com.platform.qujia.utils.StringUtils;
import com.platform.qujia.utils.exception.CustomException;
import com.platform.qujia.utils.exception.EndingException;
import com.platform.qujia.utils.redis.RedisCacheUtil;
import com.platform.qujia.utils.weixinapp.HttpRequestUtil;
import com.platform.qujia.utils.weixinapp.WeiXinUserUtil;
import net.sf.json.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

import javax.annotation.Resource;
import java.util.HashMap;
import java.util.Objects;
import java.util.concurrent.TimeUnit;

@Service
public class WeChatServiceImpl implements WeChatService {
    private static Logger logger = (Logger) LoggerFactory.getLogger(QuJiaPayV2Controller.class);

    @Resource
    private RedisCacheUtil redisCacheUtil;
    @Resource
    private EnterpriseService enterpriseService;

    @Value("${domain.adminName}")
    private String adminName;


    //客服系统退给用户消息 CUSTOMER_DIALOGUE
    private static final String CUSTOMER_DIALOGUE_RUL = "https://api.weixin.qq.com/cgi-bin/message/custom/send?access_token=ACCESS_TOKEN";

    public synchronized String getAccessToken(String appId, String appSecret) {
        //redis缓存key
        String accessTokenKey = "access_token_" + appId;
        if (!redisCacheUtil.hasKey(accessTokenKey) || StringUtils.isBlank(redisCacheUtil.getCacheObject(accessTokenKey))) {
            String token = WeiXinUserUtil.getToken(appId, appSecret).getAccessToken();
            redisCacheUtil.setCacheObject(accessTokenKey, token);
            redisCacheUtil.expire(accessTokenKey, 7100, TimeUnit.SECONDS);
            logger.info("getTokenByRedisCache-set appId " + appId + " 's token is " + token);
            return token;
        } else {
            String token = redisCacheUtil.getCacheObject(accessTokenKey);
            logger.info("getTokenByRedisCache-get appId " + appId + " 's token is " + token);
            return token;
        }
    }

    /*
     * 客服对话框推送消息
     * @param accessToken
     * @return
     */
    public void customerDialogue(String originId, String openId) {
        try {
            logger.info("--------------------------");
            Enterprise enterprise = enterpriseService.selectEnterpriseByOriginId(originId);
            if (enterprise == null || StringUtils.isBlank(enterprise.getAppId()) || StringUtils.isBlank(enterprise.getAppSecret())) {
                throw new EndingException("该油企未查到或未配置相关参数");
            }
            HashMap<String, Object> paramsHashMap = new HashMap<>();
            paramsHashMap.put("touser", openId);

            Long dialogueAdId = enterprise.getDialogueAdId();
            if (dialogueAdId == null) {
                throw new EndingException("油企未配置adId");
            }
            CustomerDialogueAdTemplate customerDialogueAdTemplate = enterpriseService.selectCustomerDialogueAdTemplateById(dialogueAdId);

            if (customerDialogueAdTemplate == null) {
                throw new EndingException("未查到ad模板");
            }
            String type = customerDialogueAdTemplate.getType();
            logger.info(customerDialogueAdTemplate.toString());
            if (StringUtils.isBlank(type)) {
                throw new EndingException("ad模板未配置type");
            }


            if ("text".equals(type)) {
                HashMap<String, Object> textHashMap = new HashMap<>();
                textHashMap.put("content", customerDialogueAdTemplate.getContent());

                paramsHashMap.put("msgtype", "text");
                paramsHashMap.put("text", textHashMap);
            } else if ("image".equals(type)) {
                HashMap<String, Object> imageHashMap = new HashMap<>();
                imageHashMap.put("media_id", customerDialogueAdTemplate.getMediaId());

                paramsHashMap.put("msgtype", "image");
                paramsHashMap.put("image", imageHashMap);
            } else if ("link".equals(type)) {
                HashMap<String, Object> linkHashMap = new HashMap<>();
                linkHashMap.put("title", customerDialogueAdTemplate.getTitle());
                linkHashMap.put("description", customerDialogueAdTemplate.getDescription());
                linkHashMap.put("url", customerDialogueAdTemplate.getUrl());
                linkHashMap.put("thumb_url", customerDialogueAdTemplate.getThumbUrl());

                paramsHashMap.put("msgtype", "link");
                paramsHashMap.put("link", linkHashMap);
            } else if ("miniprogrampage".equals(type)) {
                HashMap<String, Object> miniHashMap = new HashMap<>();
                miniHashMap.put("title", customerDialogueAdTemplate.getTitle());
                miniHashMap.put("pagepath", customerDialogueAdTemplate.getPagepath());
                miniHashMap.put("thumb_media_id", customerDialogueAdTemplate.getThumbMediaId());

                paramsHashMap.put("msgtype", "miniprogrampage");
                paramsHashMap.put("miniprogrampage", miniHashMap);
            } else {
                throw new EndingException("type类型不对");
            }


            String accessToken = this.getAccessToken(enterprise.getAppId(), enterprise.getAppSecret());
            if (StringUtils.isBlank(accessToken)) {
                throw new EndingException("accessToken获取失败");
            }
            logger.info("accessToken:" + accessToken);
            String requestUrl = CUSTOMER_DIALOGUE_RUL.replace("ACCESS_TOKEN", accessToken);
            JSONObject resultJson = HttpClientUtil.doPostJson(requestUrl, JSON.toJSONString(paramsHashMap));


            logger.info("resultJson：" + resultJson);
            logger.info("resultJson：" + resultJson.get("errcode"));
            logger.info("resultJson：" + resultJson.get("errmsg"));

            logger.info("--------------------------");
        } catch (EndingException e) {
            logger.info("customerDialogue-" + e.getMessage(), e);
        } catch (Exception e) {
            logger.info("customerDialogue-", e);
        }

    }

    /**
     * 微信同步卡包积分
     */
    @Override
    public void wxAddUserBonus(WxAddBonus wxAddBonus) {
        String accessToken = getTokenByRedisCache(wxAddBonus.getGzhAppId(), wxAddBonus.getGzhAppSecret());

        String code =
                WeiXinUserUtil.getCodeByOpenIdAndCardId(wxAddBonus.getBlogOpenid(), wxAddBonus.getCardId(), accessToken);

        WeiXinUserUtil.updateUser(code, wxAddBonus.getRecordBonus(), wxAddBonus.getBonus(), wxAddBonus.getCardId(), accessToken);
    }

    /**
     * 微信同步卡包积分
     */
    @Override
    @Async("taskExecutor")
    public void wxAddBonusByUserInfoAndEnterpriseAndAction(String recordBonus, AppUserInfo appUserInfo, Enterprise enterprise) {
        WxAddBonus wxAddBonus = new WxAddBonus();
        wxAddBonus.setRecordBonus(recordBonus);
        wxAddBonus.setBonus(appUserInfo.getIntegral());
        wxAddBonus.setBlogOpenid(appUserInfo.getBlogOpenid());
        wxAddBonus.setCardId(enterprise.getCardId());
        wxAddBonus.setGzhAppSecret(enterprise.getGzhAppSecret());
        wxAddBonus.setGzhAppId(enterprise.getGzhAppId());
        wxAddUserBonus(wxAddBonus);
    }

    /**
     * 从Redis缓存中获取 tokenCache
     *
     * @param appId
     * @param appSecret
     * @return
     */
    @Override
    public String getTokenByRedisCache(String appId, String appSecret) {
        //redis缓存key
        String accessTokenKey = "access_token_" + appId;
        if (!redisCacheUtil.hasKey(accessTokenKey) || redisCacheUtil.getCacheObject(accessTokenKey) == null || redisCacheUtil.getCacheObject(accessTokenKey).equals("")) {
            String token;
            if (Objects.isNull(appSecret)) {
                logger.info("开始调用第三方平台token");
                RestTemplate restTemplate = new RestTemplate();
                token = restTemplate.getForObject(adminName + "/prod-api/thirdParty/weChat/getAccessToken?authorizerAppid=" + appId, String.class);
                if (token == null || token.contains("\"code\":500")) {
                    logger.error("调用第三方平台token失败，appId:[{}],msg:{}", appId, token);
                    throw new CustomException(CodeMsg.THIRD_PART_AUTHORIZE_FAIL);
                }
                logger.info("第三放平台token" + token);
            } else {
                logger.info("之前逻辑token");
                token = WeiXinUserUtil.getToken(appId, appSecret).getAccessToken();
            }
            redisCacheUtil.setCacheObject(accessTokenKey, token);
            redisCacheUtil.expire(accessTokenKey, 7100, TimeUnit.SECONDS);
            logger.info("设置Redis缓存中" + appId + "的token信息: " + token);
            return token;
        } else {
            String cacheToken = redisCacheUtil.getCacheObject(accessTokenKey);
            logger.info("Redis缓存中" + appId + "的token信息: " + cacheToken);
            return cacheToken;
        }
    }

}

